/*
 * Copyright 2011-2020 the original author or authors.
 *
 * Licensed under the Apache License, Version 2.0.
 * See `LICENSE` in the project root for license information.
 */

package me.ijleex.mgmt.admin.test.redis;

import java.util.List;
import java.util.concurrent.ExecutionException;

import org.junit.jupiter.api.Test;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;

import io.lettuce.core.RedisURI;
import io.lettuce.core.SetArgs;
import io.lettuce.core.cluster.RedisClusterClient;
import io.lettuce.core.cluster.api.StatefulRedisClusterConnection;
import io.lettuce.core.cluster.api.async.RedisAdvancedClusterAsyncCommands;

/**
 * LettuceClusterFactory
 *
 * @author liym
 * @since 2019-04-09 21:10 新建
 */
public class LettuceClusterFactory {

    private static final String REDIS_KEY_PREFIX = "site:";

    private final Logger logger = LoggerFactory.getLogger(this.getClass());

    /**
     * 获取 Redis 键的个数
     * <p/>
     * <p>加载数据到 Redis</p>
     * <p>
     * <pre>
     * 使用 Redis 的 pipe mode 导入数据到 Redis
     * http://www.redis.cn/topics/mass-insert.html
     *
     * <b>cat top-1m.csv | bin/redis-cli -c -h 127.0.0.1 -p 6379 --pipe</b>
     *
     * top-1m.csv 文件内容的格式为：
     * SET site:1 google.com
     * SET site:2 youtube.com
     * ...
     *
     * MS-Windows 系统中，需要设置 top-1m.csv 文件的换行符风格为 <b>dos</b>：
     * vim: <b>set ff=dos</b>
     * </pre>
     * </p>
     *
     * @throws ExecutionException 线程执行异常
     * @throws InterruptedException 线程中断异常
     * @since 2019-03-27 13:54
     */
    @Test
    public void testGetRedisKeys() throws ExecutionException, InterruptedException {
        RedisAdvancedClusterAsyncCommands<String, String> commands = this.getRedisConnection();

        String pattern = REDIS_KEY_PREFIX + '*';
        List<String> keys = commands.keys(pattern).get();

        this.logger.debug("Redis Keys count: {} = {}", pattern, keys.size());
    }

    /**
     * 得到 Redis 连接
     *
     * @return Redis 连接（异步方式）
     * @since 2019-03-27 22:29
     */
    private RedisAdvancedClusterAsyncCommands<String, String> getRedisConnection() {
        // 连接 Redis
        RedisURI uri = RedisURI.create("127.0.0.1", 6379);
        // uri.setPassword("***".toCharArray());
        RedisClusterClient client = RedisClusterClient.create(uri);
        StatefulRedisClusterConnection<String, String> conn = client.connect();

        return conn.async();
    }

    /**
     * 为键 key 储存的数字值加上增量 increment
     *
     * @since 2019-04-09 21:03
     */
    @Test
    public void testIncrRedisValue() throws ExecutionException, InterruptedException {
        RedisAdvancedClusterAsyncCommands<String, String> commands = this.getRedisConnection();

        Long i = commands.incrby("i", 1000L).get();

        this.logger.debug("Redis IncrBy i: {}", i);

        // ===

        // 分布式锁 distlock.DistributedLock#tryLock
        SetArgs setArgs = SetArgs.Builder.ex(30).nx();
        String result = commands.set("i", "0", setArgs).get();
        this.logger.debug("Redis set nx: {}", result);
    }

}
